import { useEffect, useReducer, useRef } from 'react';
import styled from 'styled-components';
import { DispatchType, initState, reduceHandler } from './reducer';
import { VisualModel } from './VisualModel';
import { delay } from '../lib';

export default function Demo() {
  const refScreen = useRef<HTMLInputElement>(null);
  const refProcess = useRef<boolean>(false);
  const [state, dispatch] = useReducer(reduceHandler, initState());

  const onKeyDown = (e: React.KeyboardEvent) => {
    // console.log(`Key pressed: ${e.key}`);
    if ([
      '0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
      '+', '-', '*', '/', '.',
      '=', 'c'
    ].includes(e.key)) {
      dispatch({type: e.key as DispatchType})
    }
    else if (e.key === 'Enter') {
      dispatch({type: '='})
    }
  };

  const doProcess = async () => {
    // console.log('do process')
    if (!!refProcess.current) return
    refProcess.current = true
    while (state.processor.status !== 'done') {
      await delay(1000)
      dispatch({ type: '!' })
    }
    await delay(1000)
    dispatch({ type: 'c' })
    refProcess.current = false
    // console.log('done')
  }

  useEffect(() => {
    if (!!refScreen?.current) {
      refScreen.current.value = state.userInput;
    }
  }, [state.userInput]);

  useEffect(() => {
    if (state.strOperator === '=') {
      doProcess()
    }
  }, [state])

  return (
    <Wrapper tabIndex={-1} onKeyDown={onKeyDown}>
      <VisualModel state={state} />
      <Frame>
        <Screen ref={refScreen} />
        <KeyBoard>
          <KeyButton className='clear red' onClick={() => dispatch({ type: 'c' })}><i>C</i></KeyButton>
          <KeyButton onClick={() => dispatch({ type: '/' })}><i>/</i></KeyButton>
          <KeyButton onClick={() => dispatch({ type: '*' })}><i>*</i></KeyButton>

          <KeyButton onClick={() => dispatch({ type: '7' })}><i>7</i></KeyButton>
          <KeyButton onClick={() => dispatch({ type: '8' })}><i>8</i></KeyButton>
          <KeyButton onClick={() => dispatch({ type: '9' })}><i>9</i></KeyButton>
          <KeyButton onClick={() => dispatch({ type: '-' })}><i>-</i></KeyButton>

          <KeyButton onClick={() => dispatch({ type: '4' })}><i>4</i></KeyButton>
          <KeyButton onClick={() => dispatch({ type: '5' })}><i>5</i></KeyButton>
          <KeyButton onClick={() => dispatch({ type: '6' })}><i>6</i></KeyButton>
          <KeyButton className='plus' onClick={() => dispatch({ type: '+' })}><i>+</i></KeyButton>

          <KeyButton onClick={() => dispatch({ type: '1' })}><i>1</i></KeyButton>
          <KeyButton onClick={() => dispatch({ type: '2' })}><i>2</i></KeyButton>
          <KeyButton onClick={() => dispatch({ type: '3' })}><i>3</i></KeyButton>
          <KeyButton onClick={() => dispatch({ type: '0' })}><i>0</i></KeyButton>

          <KeyButton onClick={() => dispatch({ type: '00' })}><i>00</i></KeyButton>
          <KeyButton onClick={() => dispatch({ type: '.' })}><i>.</i></KeyButton>
          <KeyButton className='blue' onClick={() => dispatch({ type: '=' })}><i>=</i></KeyButton>
        </KeyBoard>
      </Frame>
    </Wrapper>
  );
}

const Wrapper = styled.main`
  background-color: #ccc;
  padding-top: 5rem;
  display: flex;
  justify-content: center;
  align-items: start;
  flex-direction: row-reverse;
  gap: 8rem;

  * {
    box-sizing: border-box;
    margin: 0;
    padding: 0;
  }
`;

const Frame = styled.div`
  background-color: #333;
  padding: 2rem;
  border-radius: 1.25rem;
  box-shadow:
    25px 25px 75px rgba(0, 0, 0, 0.25),
    10px 10px 70px rgba(0, 0, 0, 0.25),
    inset -5px -5px 15px rgba(0, 0, 0, 0.5),
    inset  5px  5px 15px rgba(0, 0, 0, 0.5)
    ;
`;

const Screen = styled.input`
  width: 100%;
  height: 120px;
  background-color: #A7AF7C;
  padding: 0 10px;
  margin-bottom: 1.25rem;
  box-shadow: 0 0 0 2px rgba(0,0,0,.75);
  font-size: 1.8rem;
  text-align: right;
`;

const KeyBoard = styled.div`
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  grid-template-rows: repeat(4, 1fr);
  gap: 1.25rem;
`;

const KeyButton = styled.button`
  cursor: pointer;
  width: 5rem;
  height: 5rem;
  place-items: center;
  border-radius: 10px;
  background: linear-gradient(180deg, #2f2f2f, #5f5f5f);
  box-shadow: 0 0 2px rgba(0,0,0,0.75),
    10px 20px 25px rgba(0,0,0,0.4),
    inset -8px 0 8px rgba(0,0,0,0.15),
    inset 0 -8px 8px rgba(0,0,0,0.25),
  ;

  &:active {
    filter: brightness(1.5);
  }

  position: relative;
  &::before {
    content: '';
    position: absolute;
    top: 4px;
    left: 6px;
    bottom: 12px;
    right: 10px;
    border-radius: 10px;  
    background: linear-gradient(90deg, #2d2d2d, #5d5d5d);
    border-left: 1px solid #000;
    border-top: 1px solid #000;
    border-bottom: 1px solid #000;
    box-shadow:
      -5px -5px 15px rgba(0,0,0,0.1),
      10px  5px 10px rgba(0,0,0,0.15)
      ;
  }

  & i {
    position: relative;
    font-size: 2em;
    font-weight: 700;
    color: #fff;
  }

  &.plus {
    grid-row: span 2; 
    height: 180px;
  }
  &.clear {
    grid-column: span 2;
    width: 180px;
  }

  &.red {
    background: #d20000;
  }
  &.red::before {
    background: linear-gradient(90deg, #d20000, #ffffff5c);
    border-left: 1px solid #fff4;
    border-top: 1px solid #fff4;
    border-bottom: 1px solid #fff4;
  }

  &.blue {
    background: #2196f3;
  }
  &.blue::before {
    background: linear-gradient(90deg, #1479c9, #ffffff5c);
    border-left: 1px solid #fff4;
    border-top: 1px solid #fff4;
    border-bottom: 1px solid #fff4;
  }
`
